/**
*@author AgendaBuddy
**/

package nmsu.ppe.agendabuddy;

import java.util.Calendar;
import java.util.Date;

import android.app.Activity;
import android.net.Uri;
import android.os.Bundle;
import android.widget.TextView;
import android.content.ContentResolver;
import android.content.ContentUris;
import android.content.Context;
import android.content.ContextWrapper;
import android.content.Intent;
import android.database.Cursor;
import android.text.format.DateUtils;
import android.view.View;
import android.view.WindowManager;

public class AgendaBuddy extends Activity {     
        private Calendar actualDate, viewDate;
        private TextView[] monthText = new TextView[42];
        private TextView[] weekText = new TextView[7];
        private DBAdapter dba = new DBAdapter(this);

        /** Called whenever the activity is created. */
        @Override
        public void onCreate(Bundle savedInstanceState)
        {
                super.onCreate(savedInstanceState);

                //Set the current date
                if(actualDate == null)  
                {
                        actualDate = Calendar.getInstance();
                }

                // Get the saved instance of viewDate if one exists
                if (getLastNonConfigurationInstance() != null)
                {
                        viewDate = (Calendar)getLastNonConfigurationInstance();
                }

                //Set the initial view date to the current date if one wasn't saved
                if(viewDate == null) 
                {
                        viewDate = Calendar.getInstance();
                }

                // set the view that will be seen
                setContentView(R.layout.main);

                // get the orientation
                int orientation = ((WindowManager) getBaseContext().getSystemService(Context.WINDOW_SERVICE))
                                .getDefaultDisplay().getOrientation();
                // init the correct view determined by the current orientation
                if (orientation == 0)
                {
                        // Portrait
                        initMonthText( monthText );
                        initMonthView( viewDate );
                } else
                        if (orientation == 1)
                        {
                                // Landscape
                                initWeekText( weekText );
                                if(viewDate.get(Calendar.MONTH) == actualDate.get(Calendar.MONTH) && 
                                                viewDate.get(Calendar.YEAR) == actualDate.get(Calendar.YEAR))
                                {
                                        // if in current month, go to current week
                                        viewDate.set(Calendar.DATE, actualDate.get(Calendar.DATE));
                                } else {
                                        // if in another month, default to the first week
                                        viewDate.set(Calendar.DATE, 1);
                                }
                                initWeekView( viewDate );
                        }         

                initCalendar( viewDate );
        }

        /** Store the instance of an object. */
        @Override
        public Object onRetainNonConfigurationInstance() 
        {
                if (viewDate != null) // Check that the object exists
                        return(viewDate);
                return super.onRetainNonConfigurationInstance();
        }

        /** Called when a child activity finishes */
/**
* @param requestCode request for info
* @param resultCode resulting info
* @param data used with getExtras()
* @return orientation portrait (month view) or landscape (week view)
**/
        protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        if (requestCode == 0) {
            if (resultCode == RESULT_OK) {
                        Bundle extras = data.getExtras();
                        viewDate = (Calendar) extras.get("Calendar");
                        // get the orientation
                        int orientation = ((WindowManager) getBaseContext().getSystemService(Context.WINDOW_SERVICE))
                                        .getDefaultDisplay().getOrientation();
                        // init the correct view determined by the current orientation
                        if (orientation == 0)
                        {
                                // Portrait
                                resetMonthBackground();
                                initMonthText( monthText );
                                initMonthView( viewDate );
                        } else
                                if (orientation == 1)
                                {
                                        // Landscape
                                        resetWeekBackground();
                                        initWeekText( weekText );
//                                      viewDate.set(Calendar.DATE, 1); // default to first week of month - can discuss this
                                        initWeekView( viewDate );
                                }         

                        initCalendar( viewDate );
            }
        }
    }

        /****** Navigating views ******/
/**
* @param v used to help navigate views
**/
        public void monthForward(View v)
        {
                viewDate.set( Calendar.MONTH, viewDate.get(Calendar.MONTH) + 1 );
                resetMonthBackground();
                initCalendar( viewDate );
                initMonthView( viewDate );
        }

        public void monthBackward(View v)
        {
                viewDate.set( Calendar.MONTH, viewDate.get(Calendar.MONTH) - 1 );
                resetMonthBackground();
                initCalendar( viewDate );
                initMonthView( viewDate );
        }

        public void weekForward(View v)
        {
                if( viewDate.getActualMaximum( Calendar.DATE ) - viewDate.get( Calendar.DATE ) < 7 ){
                        int temp = viewDate.get( Calendar.DAY_OF_WEEK );
                        viewDate.set( Calendar.DATE, viewDate.getActualMaximum( Calendar.DATE ) );
                        if( temp <= viewDate.get( Calendar.DAY_OF_WEEK ) ){
                                viewDate.set( Calendar.MONTH, viewDate.get( Calendar.MONTH ) + 1 );
                                viewDate.set( Calendar.DATE, 1 );
                        }
                } else {
                        viewDate.set( Calendar.DATE, viewDate.get( Calendar.DATE ) + 7 );
                }
                resetWeekBackground();
                initCalendar( viewDate );
                initWeekView( viewDate );
        }

        public void weekBackward(View v)
        {
                if( viewDate.get( Calendar.DATE ) <= 7 ){
                        if( viewDate.get( Calendar.DATE ) <= viewDate.get( Calendar.DAY_OF_WEEK ) ){
                                viewDate.set( Calendar.MONTH, viewDate.get( Calendar.MONTH ) - 1 );
                                viewDate.set( Calendar.DATE, viewDate.getActualMaximum( Calendar.DATE ) );
                        } else {
                                viewDate.set( Calendar.DATE, 1 );
                        }
                } else {
                        viewDate.set( Calendar.DATE, viewDate.get( Calendar.DATE ) - 7 );
                }
                resetWeekBackground();
                initCalendar( viewDate );
                initWeekView( viewDate );
        }

        /****** Click events ******/

        public void switchToDay(View v)
        {
                Intent myIntent = new Intent(v.getContext(), DayActivity.class);
                String dayIn = ( (TextView) v ).getText().toString().substring(1);
                String day = "";
                int i = 0;
                while(dayIn.length() > i && !dayIn.substring(i,i+1).equalsIgnoreCase("\n")){
                        day += dayIn.substring(i,i+1);
                        i++;
                }
                int date = Integer.parseInt( day );
                viewDate.set( Calendar.DAY_OF_MONTH, date );
                myIntent.putExtra("Calendar",viewDate);
        startActivityForResult(myIntent, 0);
        }

        /****** Google stuff ******/

        public void GoogleCalendar()
        {
            ContextWrapper context = null;
                ContentResolver contentResolver = context.getContentResolver();
             
            final Cursor cursor = contentResolver.query(Uri.parse("content://calendar/calendars"),
                    (new String[] { "_id", "displayName", "selected" }), null, null, null);
             
            while (cursor.moveToNext()) {
             
                final String _id = cursor.getString(0);
                final String displayName = cursor.getString(1);
                final Boolean selected = !cursor.getString(2).equals("0");
               
                System.out.println("Id: " + _id + " Display Name: " + displayName + " Selected: " + selected);
            }
            
            Uri.Builder builder = Uri.parse("content://calendar/instances/when").buildUpon();
            long now = new Date().getTime();
            ContentUris.appendId(builder, now - DateUtils.WEEK_IN_MILLIS);
            ContentUris.appendId(builder, now + DateUtils.WEEK_IN_MILLIS);
             
            Cursor eventCursor = contentResolver.query(builder.build(),
//                  new String[] { "title", "begin", "end", "allDay"}, "Calendars._id=" + id,
                    null, "startDay ASC, startMinute ASC", null, null);
             
            while (eventCursor.moveToNext()) {
                final String title = eventCursor.getString(0);
                final Date begin = new Date(eventCursor.getLong(1));
                final Date end = new Date(eventCursor.getLong(2));
                final Boolean allDay = !eventCursor.getString(3).equals("0");
               
                System.out.println("Title: " + title + " Begin: " + begin + " End: " + end +
                        " All Day: " + allDay);
            }


                
                
                /*String[] projection = new String[] { "_id", "name" };
                Uri calendars = Uri.parse("content://calendar/calendars");

                Cursor managedCursor = managedQuery(calendars, projection, "selected=1", null, null);

                if (managedCursor.moveToFirst()) {
                        String calName; 
                        String calId; 
                        int nameColumn = managedCursor.getColumnIndex("name"); 
                        int idColumn = managedCursor.getColumnIndex("_id");
                        do {
                                calName = managedCursor.getString(nameColumn);
                                calId = managedCursor.getString(idColumn);
                        } while (managedCursor.moveToNext());
                }

                Calendar cal = Calendar.getInstance();              
                Intent intent = new Intent(Intent.ACTION_EDIT);
                intent.setType("vnd.android.cursor.item/event");
                intent.putExtra("beginTime", cal.getTimeInMillis());
                intent.putExtra("allDay", true);
                intent.putExtra("rrule", "FREQ=YEARLY");
                intent.putExtra("endTime", cal.getTimeInMillis()+60*60*1000);
                intent.putExtra("title", "A Test Event from android app");
                startActivity(intent);*/

        }

        /****** Initialize and set date values *******/
/**
* @param c used to set calendar information (year, date, month)
**/
        public String initYear( Calendar c )
        {
                // init year
                TextView yearText = (TextView) findViewById(R.id.year_field);
                int year = c.get(Calendar.YEAR);
                if(yearText != null)
                {
                        yearText.setText( String.valueOf( year ) );
                }

                return (String) yearText.getText();
        }

        public String initMonth( Calendar c )
        {
                // init month
                TextView monthText = (TextView) findViewById(R.id.month_field);
                int month = c.get(Calendar.MONTH);
                if(monthText != null)
                {
                        switch(month)
                        {
                        case 0:
                                monthText.setText("January");
                                break;
                        case 1:
                                monthText.setText("February");
                                break;
                        case 2:
                                monthText.setText("March");
                                break;
                        case 3:
                                monthText.setText("April");
                                break;
                        case 4:
                                monthText.setText("May");
                                break;
                        case 5:
                                monthText.setText("June");
                                break;
                        case 6:
                                monthText.setText("July");
                                break;
                        case 7:
                                monthText.setText("August");
                                break;
                        case 8:
                                monthText.setText("September");
                                break;
                        case 9:
                                monthText.setText("October");
                                break;
                        case 10:
                                monthText.setText("November");
                                break;
                        case 11:
                                monthText.setText("December");
                                break;
                        default:
                                monthText.setText("Invalid Month");
                                break;
                        }
                }

                return (String) monthText.getText();
        }

        public void initCalendar( Calendar c )
        {
                initYear(c);
                initMonth(c);
        }

        /****** Initalize the views as they are called ******/

        public void initMonthView( Calendar c )
        {
                Calendar temp = (Calendar) c.clone();
                int currentDate = actualDate.get(Calendar.DAY_OF_MONTH);
                temp.set(Calendar.DAY_OF_MONTH, 1);
                int firstDay = temp.get(Calendar.DAY_OF_WEEK);

                if(firstDay == 1)
                        firstDay = 8;

                // Set day values for current month, and highlight current day
                // Also, set them to be clickable
                dba.open();
                for(int i = firstDay - 1; i < ( temp.getActualMaximum( Calendar.DAY_OF_MONTH ) + firstDay - 1 ); i++)
                {
                        monthText[i].setText( " " + String.valueOf(i+2-firstDay) );
                        if(i+2-firstDay == currentDate &&
                                        actualDate.get(Calendar.MONTH) == temp.get(Calendar.MONTH) &&
                                        actualDate.get(Calendar.YEAR) == temp.get(Calendar.YEAR) )
                        {
                                monthText[i].setBackgroundResource(R.drawable.bg_tile_current);
                                if(dba.eventsOnDay("" + viewDate.get(Calendar.MONTH) + ":" + (i+2-firstDay) + ":" + viewDate.get(Calendar.YEAR)))
                                        monthText[i].setBackgroundResource(R.drawable.event_tile_current);
                        } else
                                if(dba.eventsOnDay("" + viewDate.get(Calendar.MONTH) + ":" + (i+2-firstDay) + ":" + viewDate.get(Calendar.YEAR)))
                                {
                                        monthText[i].setBackgroundResource(R.drawable.event_tile);
                                }
                        
                        monthText[i].setClickable(true);
                }
                dba.close();
                
                // Set day values for days from the next month that appear on the calendar, and dim them
                // Also, set them to NOT be clickable
                int tempInt = 1;
                for(int i = ( temp.getActualMaximum( Calendar.DAY_OF_MONTH ) + firstDay - 1 ); i < 42; i++)
                {
                        monthText[i].setText( " " + String.valueOf(tempInt) );
                        monthText[i].setBackgroundResource(R.drawable.bg_tile_dim);
                        monthText[i].setClickable(false);
                        tempInt++;
                }

                // Set day values for days from the previous month that appear on the calendar, and dim them
                // Also, set them to NOT be clickable
                temp.set(Calendar.MONTH, temp.get(Calendar.MONTH)-1);
                int max = temp.getActualMaximum(Calendar.DAY_OF_MONTH);
                tempInt = 0;
                for(int i = firstDay - 2; i >= 0; i--)
                {
                        monthText[i].setText( " " + String.valueOf( max - tempInt ) );
                        monthText[i].setBackgroundResource(R.drawable.bg_tile_dim);
                        monthText[i].setClickable(false);
                        tempInt++;
                }
        }

        public void initWeekView( Calendar c )
        {   
                // init days for week view
                Calendar temp = (Calendar) c.clone();
                int currentDate = temp.get(Calendar.DAY_OF_MONTH);
                int currentDay = temp.get(Calendar.DAY_OF_WEEK);

                dba.open();
                
                // Set day values, and highlight current day
                for(int i = 0; i < 7; i++)
                {

                        int day = currentDate + i + 1 - currentDay;
                        String display = String.valueOf( day );
                        String line;
                        // get the day's events
                        Cursor cursor = dba.getEvent("" + viewDate.get(Calendar.MONTH) + ":" + day + ":" + viewDate.get(Calendar.YEAR));
                        if (cursor.moveToFirst())
                        {
                                do {
                                        line = cursor.getString(2);
                                        if(line.length() > 10)
                                                line = line.substring(0, 11);
                                        display += "\n" + line;
                                } while (cursor.moveToNext());

                        }
                        cursor.close();
                

                        weekText[i].setText( " " + display );
                        if(currentDay == i + 1 && 
                                        actualDate.get(Calendar.MONTH) == temp.get(Calendar.MONTH) &&
                                        actualDate.get(Calendar.YEAR) == temp.get(Calendar.YEAR) &&
                                        actualDate.get(Calendar.DATE) == temp.get(Calendar.DATE))
                        {
                                weekText[i].setBackgroundResource(R.drawable.bg_tile_current);
                        }
                        weekText[i].setClickable(true);
                }
                
                dba.close();

                // Handle special case: current week involves the earlier month
                if( currentDate < currentDay )
                {
                        temp.set(Calendar.MONTH, temp.get( Calendar.MONTH ) - 1);
                        int max = temp.getActualMaximum( Calendar.DAY_OF_MONTH );
                        for(int i = 0; i < currentDay - currentDate; i++)
                        {
                                weekText[i].setText( " " + String.valueOf( max + i + 1 + currentDate - currentDay ) );
                                if( max + i + 1 + currentDate - currentDay > 7 )
                                {
                                        weekText[i].setClickable(false);
                                        weekText[i].setBackgroundResource(R.drawable.bg_tile_dim);
                                }
                        }
                }

                // Handle special case: current week involves the later month
                if( (currentDate + 7 - currentDay) > temp.getActualMaximum( Calendar.DAY_OF_MONTH ) )
                {
                        int val;
                        for( int i = 0; i < 7; i++ )
                        {
                                val = currentDate + i + 1 - currentDay;
                                if( val > temp.getActualMaximum( Calendar.DAY_OF_MONTH ) )
                                        val -= temp.getActualMaximum( Calendar.DAY_OF_MONTH );
                                weekText[i].setText( " " + String.valueOf( val ) );
                                if( val < 7 )
                                {
                                        weekText[i].setClickable(false);
                                        weekText[i].setBackgroundResource(R.drawable.bg_tile_dim);
                                }
                        }
                }
        }

        /****** Reseting backgrounds ******/

        public void resetMonthBackground(  )
        {
                for( int i = 0; i < 42; i++ )
                {
                        monthText[i].setBackgroundResource(R.drawable.bg_tile);
                }
        }

        public void resetWeekBackground(  )
        {
                for( int i = 0; i < 7; i++ )
                {
                        weekText[i].setBackgroundResource(R.drawable.bg_tile);
                }
        }

        /****** Initialize our pool of date values ******/
/**
* @param dayText used to set up our days
**/
        public void initMonthText( TextView[] dayText )
        {
                dayText[0] = (TextView)findViewById(R.id.monthDate0);
                dayText[1] = (TextView)findViewById(R.id.monthDate1);
                dayText[2] = (TextView)findViewById(R.id.monthDate2);
                dayText[3] = (TextView)findViewById(R.id.monthDate3);
                dayText[4] = (TextView)findViewById(R.id.monthDate4);
                dayText[5] = (TextView)findViewById(R.id.monthDate5);
                dayText[6] = (TextView)findViewById(R.id.monthDate6);
                dayText[7] = (TextView)findViewById(R.id.monthDate7);
                dayText[8] = (TextView)findViewById(R.id.monthDate8);
                dayText[9] = (TextView)findViewById(R.id.monthDate9);
                dayText[10] = (TextView)findViewById(R.id.monthDate10);
                dayText[11] = (TextView)findViewById(R.id.monthDate11);
                dayText[12] = (TextView)findViewById(R.id.monthDate12);
                dayText[13] = (TextView)findViewById(R.id.monthDate13);
                dayText[14] = (TextView)findViewById(R.id.monthDate14);
                dayText[15] = (TextView)findViewById(R.id.monthDate15);
                dayText[16] = (TextView)findViewById(R.id.monthDate16);
                dayText[17] = (TextView)findViewById(R.id.monthDate17);
                dayText[18] = (TextView)findViewById(R.id.monthDate18);
                dayText[19] = (TextView)findViewById(R.id.monthDate19);
                dayText[20] = (TextView)findViewById(R.id.monthDate20);
                dayText[21] = (TextView)findViewById(R.id.monthDate21);
                dayText[22] = (TextView)findViewById(R.id.monthDate22);
                dayText[23] = (TextView)findViewById(R.id.monthDate23);
                dayText[24] = (TextView)findViewById(R.id.monthDate24);
                dayText[25] = (TextView)findViewById(R.id.monthDate25);
                dayText[26] = (TextView)findViewById(R.id.monthDate26);
                dayText[27] = (TextView)findViewById(R.id.monthDate27);
                dayText[28] = (TextView)findViewById(R.id.monthDate28);
                dayText[29] = (TextView)findViewById(R.id.monthDate29);
                dayText[30] = (TextView)findViewById(R.id.monthDate30);
                dayText[31] = (TextView)findViewById(R.id.monthDate31);
                dayText[32] = (TextView)findViewById(R.id.monthDate32);
                dayText[33] = (TextView)findViewById(R.id.monthDate33);
                dayText[34] = (TextView)findViewById(R.id.monthDate34);
                dayText[35] = (TextView)findViewById(R.id.monthDate35);
                dayText[36] = (TextView)findViewById(R.id.monthDate36);
                dayText[37] = (TextView)findViewById(R.id.monthDate37);
                dayText[38] = (TextView)findViewById(R.id.monthDate38);
                dayText[39] = (TextView)findViewById(R.id.monthDate39);
                dayText[40] = (TextView)findViewById(R.id.monthDate40);
                dayText[41] = (TextView)findViewById(R.id.monthDate41);
        }

        public void initWeekText( TextView[] dayText )
        {

                dayText[0] = (TextView)findViewById(R.id.weekDate0);
                dayText[1] = (TextView)findViewById(R.id.weekDate1);
                dayText[2] = (TextView)findViewById(R.id.weekDate2);
                dayText[3] = (TextView)findViewById(R.id.weekDate3);
                dayText[4] = (TextView)findViewById(R.id.weekDate4);
                dayText[5] = (TextView)findViewById(R.id.weekDate5);
                dayText[6] = (TextView)findViewById(R.id.weekDate6);
        }
}